package com.yanqu.road.server.gameplayer.module.activity.festivalgift;

import com.yanqu.road.entity.activity.ActivityConditionInfo;
import com.yanqu.road.entity.activity.ActivityInfo;
import com.yanqu.road.entity.activity.festivalgift.FestivalGiftData;
import com.yanqu.road.entity.config.goods.MallInfo;
import com.yanqu.road.entity.enums.eActivityType;
import com.yanqu.road.entity.enums.ePlayerAttrType;
import com.yanqu.road.entity.enums.eSystemId;
import com.yanqu.road.logic.bussiness.activity.FestivalGiftBusiness;
import com.yanqu.road.logic.bussiness.activity.FiveHeroBusiness;
import com.yanqu.road.pb.activity.FestivalGiftProto;
import com.yanqu.road.server.GameServer;
import com.yanqu.road.server.gameplayer.GamePlayer;
import com.yanqu.road.server.gameplayer.module.activity.ActivityMallModule;
import com.yanqu.road.server.gameplayer.module.base.GeneralModule;
import com.yanqu.road.server.gameplayer.module.player.AttributeModule;
import com.yanqu.road.server.gameplayer.module.player.RechargeModule;
import com.yanqu.road.server.manger.ServerListMgr;
import com.yanqu.road.server.manger.activity.ActivityMgr;
import com.yanqu.road.server.manger.activity.NormalActivityMgr;
import com.yanqu.road.server.manger.config.SystemOpenMgr;
import com.yanqu.road.server.protocol.ClientProtocol;
import com.yanqu.road.server.protocol.GameErrorCode;
import com.yanqu.road.utils.property.Property;
import com.yanqu.road.utils.property.PropertyHelper;
import com.yanqu.road.utils.string.StringUtils;
import java.math.BigInteger;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @Description 节日自选礼包
 * @Author cwj
 * @Data 2023/7/24 14:50
 */
public class FestivalGiftModule extends GeneralModule {

    /**
     * 自选商品MAP，k：活动ID,v：礼包自选道具
     */
    private Map<Integer, Map<Integer, FestivalGiftData>> activitySelectPropsMap = new ConcurrentHashMap<>();

    //自选礼包t_s_activity_mall表，extendParam数组下标
    private int selectPropIndex = 4;

    public FestivalGiftModule(GamePlayer player) {
        super(player);
    }

    @Override
    public boolean loadData() {
        List<ActivityInfo> activityList = NormalActivityMgr.getOpenActivityInfoList(eActivityType.FestivalGift.getValue());
        for (ActivityInfo activityInfo : activityList) {
            //读取数据库数据
            Map<Integer, FestivalGiftData> map = FestivalGiftBusiness.getFestivalGiftDataMap(activityInfo.getActivityId(), player.getUserId());
            activitySelectPropsMap.put(activityInfo.getActivityId(), map);
        }
        return true;
    }

    @Override
    public boolean afterLoadData() {
        return false;
    }

    @Override
    public boolean saveData() {
        if(activitySelectPropsMap.size() > 0){
            for (Map<Integer, FestivalGiftData> mallMap : activitySelectPropsMap.values()) {
                for (FestivalGiftData festivalGiftData : mallMap.values()) {
                    if(festivalGiftData.isInsertOption()){
                        FestivalGiftBusiness.addFestivalGiftData(festivalGiftData);
                    }else if(festivalGiftData.isUpdateOption()){
                        FestivalGiftBusiness.updateFestivalGiftData(festivalGiftData);
                    }
                }
            }
        }
        return true;
    }

    @Override
    public void afterLogin() {
        this.initActivityMallMap();
        //同步礼包数据
        List<ActivityInfo> activityList = NormalActivityMgr.getOpenActivityInfoList(eActivityType.FestivalGift.getValue());
        for (ActivityInfo activityInfo : activityList) {
            this.getMallList(activityInfo.getActivityId());
        }
    }

    /**
     * 初始化礼包MAP
     */
    public void initActivityMallMap() {
        Map<Integer, Map<Integer, MallInfo>> allMallMap = ActivityMgr.getAllActivityMallInfoMap();
        //判断是否活动是否存在
        List<ActivityInfo> activityList = NormalActivityMgr.getOpenActivityInfoList(eActivityType.FestivalGift.getValue());
        for (ActivityInfo activityInfo : activityList) {
            Map<Integer, MallInfo> mallInfoMap = allMallMap.get(activityInfo.getActivityId());
            //判断自选礼包是否存在,存在的情况下就不在生成
            Map<Integer, FestivalGiftData> userMallMap = this.activitySelectPropsMap.get(activityInfo.getActivityId());
            if (userMallMap != null && userMallMap.size() > 0) {
                continue;
            }
            userMallMap = new ConcurrentHashMap<>();
            //获取活动规则
            List<ActivityConditionInfo> conditionInfoList = NormalActivityMgr.getActivityConditionInfoList(activityInfo.getActivityId());
            for (ActivityConditionInfo conditionInfo : conditionInfoList) {
                boolean flag = this.checkMallCondition(conditionInfo.getParamList());
                if (flag) {
                    //触发的礼包
                    String[] mallUnIdArr = conditionInfo.getExtendParam().split("\\|");
                    for (String mallUnIdStr : mallUnIdArr) {
                        int mallUnId = Integer.valueOf(mallUnIdStr);
                        MallInfo mallInfo = this.getMallInfoByUnId(mallInfoMap, mallUnId);
                        if (mallInfo != null) {
                            FestivalGiftData festivalGiftData = new FestivalGiftData();
                            festivalGiftData.setActivityId(activityInfo.getActivityId());
                            festivalGiftData.setUserId(getUserId());
                            festivalGiftData.setMallId(mallInfo.getMallId());
                            festivalGiftData.setProp(null);
                            festivalGiftData.setBuyNum(0);
                            festivalGiftData.setInsertOption();
                            if (!userMallMap.containsKey(mallInfo.getMallId())) {
                                userMallMap.put(mallInfo.getMallId(), festivalGiftData);
                            }
                        }
                    }
                }
            }
            //无满足任何礼包的情况下，注入个空礼包，标志已经触发过
            if (userMallMap.size() <= 0) {
                FestivalGiftData festivalGiftData = new FestivalGiftData();
                festivalGiftData.setActivityId(activityInfo.getActivityId());
                festivalGiftData.setUserId(getUserId());
                festivalGiftData.setMallId(-1);
                festivalGiftData.setProp(null);
                festivalGiftData.setBuyNum(0);
                festivalGiftData.setInsertOption();
                userMallMap.put(festivalGiftData.getMallId(), festivalGiftData);
            }
            this.activitySelectPropsMap.put(activityInfo.getActivityId(), userMallMap);
            log.info("自选礼包初始化：{}，{}", player.getUserId(), this.activitySelectPropsMap);
        }
    }

    /**
     * 获取礼包列表
     * @param activityId
     * @return
     */
    public int getMallList(int activityId) {
        ActivityInfo activityInfo = ActivityMgr.getOpenActivityInfo(activityId);
        //活动是否存在
        if (activityInfo == null) {
            return GameErrorCode.E_SELF_SELECT_GIFT_ACTIVITY_NOT_EXIST_ERROR;
        }
        //PB返回
        FestivalGiftProto.FestivalGiftGetMallListRespMsg.Builder respMsg = FestivalGiftProto.FestivalGiftGetMallListRespMsg.newBuilder();
        respMsg.setRet(0);
        //礼包MAP
        Map<Integer, FestivalGiftData> mallMap = this.activitySelectPropsMap.get(activityId);
        for (FestivalGiftData festivalGiftData: mallMap.values()) {
            if (festivalGiftData.getMallId() <= 0) {
                continue;
            }
            //判断是否已经达到限购次数
            MallInfo mallInfo = NormalActivityMgr.getActivityMallInfo(activityId, festivalGiftData.getMallId());
            if (mallInfo == null) {
                continue;
            }
            //礼包可购买次数
            int canBuyTime = player.getModule(ActivityMallModule.class).getLimitCount(mallInfo);
            if (canBuyTime <= 0) {
                continue;
            }
            //pb item
            FestivalGiftProto.FestivalGiftSelectMallItem.Builder item = FestivalGiftProto.FestivalGiftSelectMallItem.newBuilder();
            item.setMallId(festivalGiftData.getMallId());
//            if (!StringUtils.isNullOrEmpty(festivalGiftData.getProp())) {
//                item.setProps(festivalGiftData.getProp());
//            }
            item.addAllIndex(festivalGiftData.getPropIndexList());
            item.setCanBuyNum(canBuyTime);
            respMsg.addMallList(item);
        }
        player.sendPacket(ClientProtocol.U_ACTIVITY_SELF_SELECT_GIFT_GET_MALL_LIST, respMsg);
        return 0;
    }

    /**
     * 添加礼包自选商品
     * @param activityId
     * @param mallId
     * @param indexList
     */
    public int addSelfSelectProp(int activityId, int mallId, List<Integer> indexList) {
        ActivityInfo activityInfo = ActivityMgr.getOpenActivityInfo(activityId);
        //活动是否存在
        if (activityInfo == null) {
            return GameErrorCode.E_SELF_SELECT_GIFT_ACTIVITY_NOT_EXIST_ERROR;
        }
        //礼包是否存在
        Map<Integer, FestivalGiftData> mallMap = this.activitySelectPropsMap.get(activityId);
        if (mallMap == null) {
            return GameErrorCode.E_SELF_SELECT_GIFT_MALL_NOT_EXIST_ERROR;
        }
        if (!mallMap.containsKey(mallId)) {
            return GameErrorCode.E_SELF_SELECT_GIFT_MALL_NOT_EXIST_ERROR;
        }
        //礼包是否存在
        MallInfo mallInfo = NormalActivityMgr.getActivityMallInfo(activityId, mallId);
        if (mallInfo == null) {
            return GameErrorCode.E_SELF_SELECT_GIFT_MALL_NOT_EXIST_ERROR;
        }
        //判断是否选满自选框
        int canSelectNum = this.getCanSelectNum(mallInfo);
        if (canSelectNum != indexList.size()) {
            return GameErrorCode.E_SELF_SELECT_GIFT_NOT_SELECT_ENOUGH;
        }
        //判断所选道具是否存在
        Map<Integer, BigInteger> realSelectMap = new LinkedHashMap<>();
        int positionIndex = 0;
        for (int index : indexList) {
            Property selectProp = this.getMallSelectPropByIndex(mallInfo, positionIndex, index);
            if (selectProp == null) {
                return GameErrorCode.E_SELF_SELECT_GIFT_SELECT_PROP_ERROR;
            }
            for (Map.Entry<Integer, BigInteger> entry : selectProp.getGoods().entrySet()) {
                int propId = entry.getKey();
                BigInteger propNum = entry.getValue();
                realSelectMap.put(propId, propNum);
            }
            positionIndex++;
        }
        String realSelectPropStr = PropertyHelper.parsePropertyMapToString(realSelectMap, ";");

        FestivalGiftData festivalGiftData = mallMap.get(mallId);
        festivalGiftData.setProp(realSelectPropStr);
        festivalGiftData.setPropIndexList(indexList);
        //记录自选商品
        mallMap.put(mallId, festivalGiftData);
        this.activitySelectPropsMap.put(activityId, mallMap);
        //PB返回
        FestivalGiftProto.FestivalGiftSelectPropRespMsg.Builder respMsg = FestivalGiftProto.FestivalGiftSelectPropRespMsg.newBuilder();
        respMsg.setRet(0);
        player.sendPacket(ClientProtocol.U_ACTIVITY_SELF_SELECT_GIFT_SELECT_PROP, respMsg);
        return 0;
    }

    /**
     * 获取礼包自选的商品
     * @param activityId
     * @param mallId
     * @return
     */
    public Property getSelectedProperty(int activityId, int mallId) {
        Map<Integer, FestivalGiftData> mallMap = this.activitySelectPropsMap.get(activityId);
        if (mallMap != null) {
            FestivalGiftData festivalGiftData = mallMap.get(mallId);
            if(null == festivalGiftData){
                return null;
            }
            return PropertyHelper.parseStringToProperty(festivalGiftData.getProp());
        }
        return null;
    }

    /**
     * 购买成功处理
     * @param activityId
     * @param mallId
     * @return
     */
    public String successBuy(int activityId, int mallId) {
        String rewardStr = "";
        Map<Integer, FestivalGiftData> mallMap = this.activitySelectPropsMap.get(activityId);
        if (mallMap != null) {
            FestivalGiftData festivalGiftData = mallMap.get(mallId);
            if (festivalGiftData != null) {
                rewardStr = festivalGiftData.getProp();
                //礼包增加购买次数
                int newNum = festivalGiftData.getBuyNum() + 1;
                festivalGiftData.setBuyNum(newNum);
            }
        }
        return rewardStr;
    }

    /**
     * 检查是否符合购买礼包条件
     * @param paramList 条件数组
     * @return
     */
    private boolean checkMallCondition(List<BigInteger> paramList) {
        //开服时间是否符合
        int openServerDay = ServerListMgr.getServerOpenDay(GameServer.getInstance().getServerId());
        long startTime = paramList.get(0).longValue();
        long endTime = paramList.get(1).longValue();
        if (!(openServerDay >= startTime && (endTime == -1 || openServerDay <= endTime))) {
            return false;
        }
        //身份等级是否符合
        long startIdentityLevel = paramList.get(2).longValue();
        long endIdentityLevel = paramList.get(3).longValue();
        if (!(player.getTitleId() >= startIdentityLevel && (endIdentityLevel == -1 || player.getTitleId() <= endIdentityLevel))) {
            return false;
        }
        //充值次数
        long startRechargeNum = paramList.get(4).longValue();
        long endRechargeNum = paramList.get(5).longValue();
        AttributeModule attributeModule = player.getModule(AttributeModule.class);
        long rechargeTimes = attributeModule.getAttribute(ePlayerAttrType.RechargeTotalTimes);
        if (!(rechargeTimes >= startRechargeNum && (endRechargeNum == -1 || rechargeTimes <= endRechargeNum ))) {
            return false;
        }
        //vip经验
        long vipExp = player.getUserInfo().getVipExp();
        long startVipExp = paramList.get(6).longValue();
        long endVipExp = paramList.get(7).longValue();
        if (!(vipExp >= startVipExp && (endVipExp == -1 || vipExp <= endVipExp))) {
            return false;
        }
        //最近30天增加的VIP经验
        long addVipExp = player.getModule(RechargeModule.class).getRecentAddVipExp(2592000000L);
        long startAddVipExp = paramList.get(8).longValue();
        long endAddVipExp = paramList.get(9).longValue();
        if (!(addVipExp >= startAddVipExp && (endAddVipExp == -1 || addVipExp <= endAddVipExp))) {
            return false;
        }
        return true;
    }

    /**
     * 获取自选格的商品LIST
     * @param mallInfo
     * @param positionIndex 自选格下标
     * @return 道具ID=数量,系统ID
     */
    private List<String> getMallCanSelectProp(MallInfo mallInfo, int positionIndex) {
        String[] extendParamArr = mallInfo.getExtendParam().split("\\|");
        if (positionIndex + this.selectPropIndex > extendParamArr.length) {
            return null;
        }
        String propStr = extendParamArr[positionIndex + this.selectPropIndex];
        return StringUtils.stringToStringList(propStr, ";");
    }

    /**
     * 获取选择的道具根据下标
     * @param mallInfo
     * @param positionIndex
     * @param propIndex
     * @return
     */
    private Property getMallSelectPropByIndex(MallInfo mallInfo, int positionIndex, int propIndex) {
        List<String> propList = this.getMallCanSelectProp(mallInfo, positionIndex);
        if (propList == null) {
            return null;
        }
        if (propList.size() <= propIndex) {
            return null;
        }
        String propStrItem = propList.get(propIndex);
        //7.6.0修改，propStrItem = 道具ID=数量,系统ID
        String[] propSystemArr = propStrItem.split(",");
        if (propSystemArr.length == 1) {
            return PropertyHelper.parseStringToProperty(propSystemArr[0]);
        } else if (propSystemArr.length >= 2){
            //判断系统是否解锁
            int systemId = Integer.parseInt(propSystemArr[1]);
            if (SystemOpenMgr.systemOpen(player, systemId)) {
                return PropertyHelper.parseStringToProperty(propSystemArr[0]);
            }
        }
        return null;
    }

    /**
     * 获取礼包可自选择的道具数
     * @param mallInfo
     * @return
     */
    private int getCanSelectNum(MallInfo mallInfo) {
        String[] extendParamArr = mallInfo.getExtendParam().split("\\|");
        return extendParamArr.length - this.selectPropIndex;
    }

    /**
     * 获取唯一标识ID
     * @param mallInfo
     * @return
     */
    private int getSelfSelectId(MallInfo mallInfo) {
        String[] extendParamArr = mallInfo.getExtendParam().split("\\|");
        return Integer.valueOf(extendParamArr[0]);
    }

    /**
     * 获取礼包，根据定义的唯一ID
     * @param mallInfoMap
     * @param unId
     * @return
     */
    private MallInfo getMallInfoByUnId(Map<Integer, MallInfo> mallInfoMap, int unId) {
        for (MallInfo mallInfo : mallInfoMap.values()) {
            int mallUnId = this.getSelfSelectId(mallInfo);
            if (unId == mallUnId) {
                return mallInfo;
            }
        }
        return null;
    }
}
